#include "pricedelegate.h"

#include "invalidprice.h"

#include <QDoubleSpinBox>

#include <QStyleOptionViewItem>
#include <QAbstractItemModel>
#include <QModelIndex>

#include <math.h>


PriceDelegate::PriceDelegate(QObject *parent)
:   QStyledItemDelegate(parent)
{
}

QWidget *PriceDelegate::createEditor(
    QWidget *parent
,   const QStyleOptionViewItem &item
,   const QModelIndex &) const
{
    QDoubleSpinBox *editor = new QDoubleSpinBox(parent);

    editor->setPrefix("    ");
    editor->setSuffix("    ");

    editor->setMaximum(99999999);
    editor->setMinimum(0);

    editor->setAlignment(item.displayAlignment);

    return editor;
}

void PriceDelegate::setEditorData(
    QWidget *editor
,   const QModelIndex &index) const
{
    int value = index.model()->data(index, PriceDelegate::dataRole()).toInt();

    QDoubleSpinBox *spinBox = dynamic_cast<QDoubleSpinBox*>(editor);
    spinBox->setValue(value * 0.01);
    spinBox->setAlignment(Qt::AlignRight);
}

void PriceDelegate::setModelData(
    QWidget *editor
,   QAbstractItemModel *model
,   const QModelIndex &index) const
{
    QDoubleSpinBox *spinBox = dynamic_cast<QDoubleSpinBox*>(editor);

    spinBox->interpretText();
    int value = spinBox->value() * 100 + 0.5;

    if(model->data(index, dataRole()).toInt() == INVALID_PRICE
    && value == 0)
        value = INVALID_PRICE;

    model->setData(index, value, dataRole());
    model->setData(index, textFromValue(value), Qt::EditRole);
}

void PriceDelegate::updateEditorGeometry(
    QWidget *editor
,   const QStyleOptionViewItem &option
,   const QModelIndex &) const
{
    editor->setGeometry(option.rect);
}

const QString PriceDelegate::textFromValue(int price)
{
    if(INVALID_PRICE == price)
        return QString("    -    ");

    int i = price / 100;
    const int f = price - i * 100;

    QLocale locale;
    const QChar decimalPoint(locale.decimalPoint());
    const QChar separatorPoint(decimalPoint == '.' ? ',' : '.');

    QString s = QString("%1%2")
        .arg(decimalPoint)
        .arg(QString::number(f), 2, QLatin1Char('0'));

    if(i > 0)
    {
        const int numDecimals = log10((double)i);
        int numSeparators = numDecimals / 3;

        while(numSeparators)
        {
            s.prepend(QString("%1%2")
                .arg(separatorPoint)
                .arg(i - static_cast<int>(i / 1000) * 1000));

            i /= 1000;
            --numSeparators;
        }
        s.prepend(QString::number(i));
    }
    else
        s.prepend("0");

    s.prepend("    ");
    s.append("    ");
    return s;
}

const int PriceDelegate::dataRole()
{
    return Qt::UserRole + 1;
}
